package org.orbis.structure;

public final class ContentInfo{
	private static ContentInfo instance;

	private String[] binaryFlagNames;
	private int binaryFlags;
	private String[] integerFlagNames;
	private int integerFlags;
	private String[] longFlagNames;
	private int longFlags;
	private String[] floatFlagNames;
	private int floatFlags;
	private String[] contentNames;
	private int contents;
	private String[] appendixNames;
	private int appendices;

	private ContentInfo(){}

	public static ContentInfo setInstance(String[] content, String[] appendix, String[] binaryFlag,
		String[] integerFlag, String[] longFlag, String[] floatFlag){
		instance = new ContentInfo();
		if(content == null) throw new IllegalArgumentException("Content must not be empty.");
		instance.contentNames = content;
		instance.contents = content.length;
		instance.appendixNames = appendix;
		instance.appendices = appendix == null? 0: appendix.length;
		instance.binaryFlagNames = binaryFlag;
		instance.binaryFlags = binaryFlag == null? 0: binaryFlag.length;
		instance.integerFlagNames = integerFlag;
		instance.integerFlags = integerFlag == null? 0: integerFlag.length;
		instance.longFlagNames = longFlag;
		instance.longFlags = longFlag == null? 0: longFlag.length;
		instance.floatFlagNames = floatFlag;
		instance.floatFlags = floatFlag == null? 0: floatFlag.length;

		return instance;
	}

	public String contentName(int index){
		if(index < contentNames.length) return contentNames[index];
		return null;
	}

	public int contentIndex(String str){
		if(str.equals("all")) return Integer.MAX_VALUE;
		for(int i = 0; i < contentNames.length; i++){
			if(contentNames[i].equalsIgnoreCase(str)) return i;
		}
		return -1;
	}

	public String appendixName(int index){
		if(index < appendixNames.length) return appendixNames[index];
		return null;
	}

	public int appendixIndex(String str){
		for(int i = 0; i < appendixNames.length; i++){
			if(appendixNames[i].equalsIgnoreCase(str)) return i;
		}

		return -1;
	}

	public String binaryFlagName(int index){
		if(index < binaryFlagNames.length) return binaryFlagNames[index];
		return null;
	}

	public int binaryFlagIndex(String str){
		for(int i = 0; i < binaryFlagNames.length; i++){
			if(binaryFlagNames[i].equalsIgnoreCase(str)) return i;
		}

		return -1;
	}

	public String integerFlagName(int index){
		if(index < integerFlagNames.length) return integerFlagNames[index];
		return null;
	}

	public int integerFlagIndex(String str){
		for(int i = 0; i < integerFlagNames.length; i++){
			if(integerFlagNames[i].equalsIgnoreCase(str)) return i;
		}

		return -1;
	}

	public String longFlagName(int index){
		if(index < longFlagNames.length) return longFlagNames[index];
		return null;
	}

	public int longFlagIndex(String str){
		for(int i = 0; i < longFlagNames.length; i++){
			if(longFlagNames[i].equalsIgnoreCase(str)) return i;
		}

		return -1;
	}

	public String floatFlagName(int index){
		if(index < floatFlagNames.length) return floatFlagNames[index];
		return null;
	}

	public int floatFlagIndex(String str){
		for(int i = 0; i < floatFlagNames.length; i++){
			if(floatFlagNames[i].equalsIgnoreCase(str)) return i;
		}

		return -1;
	}

	public int contentsNum(){
		return contents;
	}

	public int appendixNum(){
		return appendices;
	}

	public int binaryFlagNum(){
		return binaryFlags;
	}

	public int integerFlagNum(){
		return integerFlags;
	}

	public int longFlagNum(){
		return longFlags;
	}

	public int floatFlagNum(){
		return floatFlags;
	}

	public int totalNum(){
		return contents + appendices + binaryFlags + integerFlags + longFlags + floatFlags;
	}

	// Returns needed bytes to represent all serialised flag
	public int flagBytes(){
		return (int)Math.ceil(0.125 * binaryFlags) + (4 * integerFlags) + (8 * longFlags) + (4 * floatFlags);
	}
}
